From 38848a705eb4b835f62861b7d4e18c55d7c1a5ab Mon Sep 17 00:00:00 2001 From: oliskoli Date: Mon, 20 Aug 2007 22:09:14 +0000 Subject: [PATCH] Add GPS data generator (hidden input format). git-svn-id: http://gpsbabel.googlecode.com/svn/trunk@2954 f51c46e8-681c-474f-0cfe-069cfd0219fb --- gpsbabel/random.c | 208 ++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 208 insertions(+) create mode 100644 gpsbabel/random.c diff --git a/gpsbabel/random.c b/gpsbabel/random.c new file mode 100644 index 000000000..199aa5b4c --- /dev/null +++ b/gpsbabel/random.c @@ -0,0 +1,208 @@ +/* + random - GPS data generator + + Copyright (C) 2007 Olaf Klein, o.b.klein@gpsbabel.org + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111 USA +*/ + +#include "defs.h" +#include "garmin_fs.h" +#include "jeeps/gpsmath.h" +#include + +#define MYNAME "random" + +static char *opt_points, *opt_seed; + +static arglist_t random_args[] = { + { "points", &opt_points, "Generate # points", NULL, + ARGTYPE_INT, "1", NULL }, + { "seed", &opt_seed, "Starting seed of the internal number generator", NULL, + ARGTYPE_INT, "1", NULL }, + ARG_TERMINATOR +}; + + +static double +rand_dbl(const double max) +{ + return max * rand() / (((double)RAND_MAX) + 1); +} + +static int +rand_int(const int max) +{ + return (int)((double)max * rand() / (((double)RAND_MAX) + 1)); +} + +/* rand_str always returns a valid string with len >= 0 */ + +static char * +rand_str(const int maxlen, const char *fmt) +{ + char *res; + int i, len; + + len = rand_int(maxlen) + 1; + + res = xmalloc(len + 1); + res[len] = '\0'; + + for (i = 0; i < len; i++) { + int c = rand_int(26 + 26 + 10); + if ( c < 26 ) + c += 'a'; + else if (c < 52) + c = (c - 26) + 'A'; + else + c = (c - 52) + '0'; + res[i] = c; + } + if (fmt) { + char *tmp; + xasprintf(&tmp, fmt, res); + xfree(res); + return tmp; + } + else + return res; +} + +static void +random_rd_init(const char *fname) +{ +} + +static void +random_rd_deinit(void) +{ +} + +static void +random_read(void) +{ +#define RND(a) (rand_int(a) > 0) + + int i, points; + route_head *head; + waypoint *prev = NULL; + time_t time = gpsbabel_time; + + if (opt_seed) + srand(atoi(opt_seed)); + else + srand(gpsbabel_now); + + + points = (opt_points) ? atoi(opt_points) : rand_int(128) + 1; + if (doing_trks || doing_rtes) { + head = route_head_alloc(); + if (doing_trks) { + head->rte_name = rand_str(8, "Trk_%s"); + track_add_head(head); + } + else { + head->rte_name = rand_str(8, "Rte_%s"); + route_add_head(head); + } + head->rte_desc = rand_str(16, NULL); + } + else head = NULL; + + for (i = 0; i < points; i++) { + + waypoint *wpt; + garmin_fs_t *gmsd; + + wpt = waypt_new(); + gmsd = garmin_fs_alloc(-1); + fs_chain_add(&wpt->fs, (format_specific_data *) gmsd); + + do { + wpt->shortname = rand_str(8, "Wpt_%s"); + } while (wpt->shortname == NULL); + + wpt->latitude = rand_dbl(180) - 90; + wpt->longitude = rand_dbl(360) - 180; + + /* !!! "if RND(3) ..." produces some leaks in generated data !!! */ + + if RND(3) wpt->altitude = rand_int(1000) / 10; + if RND(3) WAYPT_SET(wpt, temperature, rand_int(320) / 10.0); + if RND(3) WAYPT_SET(wpt, proximity, rand_int(10000) / 10.0); + if RND(3) WAYPT_SET(wpt, depth, rand_int(10000) / 10.0); + + wpt->creation_time = time; + if RND(3) wpt->microseconds = rand_int(1000) * 1000; + time += rand_int(10) + 1; + + if (doing_trks) { + if (i > 0) { + wpt->latitude = prev->latitude + (rand_dbl(1) / 1000); + wpt->longitude = prev->longitude + (rand_dbl(1) / 1000); + WAYPT_SET(wpt, course, waypt_course(prev, wpt)); + WAYPT_SET(wpt, speed, waypt_speed(prev, wpt)); + } + wpt->sat = rand_int(12 + 1); + wpt->hdop = (rand_int(500)) / 10.0; + wpt->vdop = (rand_int(500)) / 10.0; + wpt->pdop = (rand_int(500)) / 10.0; + wpt->fix = rand_int(6) - 1; + if RND(3) wpt->cadence = rand_int(255); + if RND(3) wpt->heartrate = rand_int(255); + } + else { + if (doing_rtes && (i > 0)) { + wpt->latitude = prev->latitude + (rand_dbl(1) / 100); + wpt->longitude = prev->longitude + (rand_dbl(1) / 100); + } + if RND(3) wpt->description = rand_str(16, "Des_%s"); + if RND(3) wpt->notes = rand_str(16, "Nts_%s"); + if RND(3) GMSD_SET(addr, rand_str(8, "Adr_%s")); + if RND(3) GMSD_SET(city, rand_str(8, "Cty_%s")); + if RND(3) GMSD_SET(facility, rand_str(8, "Fac_%s")); + if RND(3) GMSD_SET(country, rand_str(8, "Ctr_%s")); + if RND(3) GMSD_SET(state, rand_str(8, "Sta_%s")); + if RND(3) GMSD_SET(phone_nr, rand_str(8, "Pnr_%s")); + if RND(3) GMSD_SET(postal_code, rand_str(8, "Pcd_%s")); + } + + if (doing_trks) track_add_wpt(head, wpt); + else if (doing_rtes) route_add_wpt(head, wpt); + else waypt_add(wpt); + + prev = wpt; + } +} + + +ff_vecs_t random_vecs = { + ff_type_internal, + { + ff_cap_read /* waypoints */, + ff_cap_read /* tracks */, + ff_cap_read /* routes */ + }, + random_rd_init, + NULL, /* wr_init */ + random_rd_deinit, + NULL, /* wr_deinit */ + random_read, + NULL, /* write */ + NULL, /* exit */ + random_args, + CET_CHARSET_ASCII, 1 /* fixed */ +}; -- 2.30.2